package core;

import java.net.InetAddress;
import java.net.InetSocketAddress;
import java.net.UnknownHostException;

import log.ServerLogger;
import org.apache.mina.core.future.ConnectFuture;
import org.apache.mina.core.session.IdleStatus;
import org.apache.mina.core.session.IoSession;
import org.apache.mina.filter.codec.ProtocolCodecFilter;
import org.apache.mina.filter.keepalive.KeepAliveFilter;
import org.apache.mina.filter.keepalive.KeepAliveMessageFactory;
import org.apache.mina.filter.keepalive.KeepAliveRequestTimeoutHandler;
import org.apache.mina.transport.socket.SocketConnector;
import org.apache.mina.transport.socket.nio.NioSocketConnector;

import ui.ServerMainFrame;
import filter.ClientTextFactory;
import filter.KeepAliveMessageFactoryImpl;
import filter.KeepAliveRequestTimeoutHandlerImpl;

public class Client implements Runnable
{
	/**
	 * @param args
	 */
	java.net.InetAddress address = null;
	public boolean isconnected() {
		return getAcceptor().connect().getSession().isConnected();
	}
	private static SocketConnector connector = null;
	private static IoSession session = null;
	private static ConnectFuture future;

	private static Client instance ;

	public static Client getInstance() {
		if(instance==null){
			ServerLogger.INFO("正在初始化服务器的缓存组件....");
			instance = new  Client();
		}
		return instance;
	}

	public Client() {
		

	}

	public SocketConnector getAcceptor(){
		if(null==connector){
			// 创建非阻塞的server端的Socket连接
			connector = new NioSocketConnector();
		}
		return connector;
	}

	public IoSession getIoSession(){
		return future.getSession();
	}

	public void send2pc(String msgstr)
	{
		
		IoSession sess = getIoSession();
		if(sess == null)
		{
			ServerLogger.Error("sess null无此session，发送失败！");
		}else
		{
			if(sess.isConnected())
			{
				sess.write(msgstr);
			}else
			{
				ServerLogger.Error("上位机未连接，发送失败！");
				//MinaServer.getInstance().sendErro("aa",session);
			}
		}
		

	}

	public void run() {
		// TODO Auto-generated method stub
		initClient();
		try {
			startClient();
		} catch (InterruptedException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	public void initClient()
	{
		Global global = Global.getInstance();
		getAcceptor().getSessionConfig().setReadBufferSize(2048);
		getAcceptor().getFilterChain().addLast("codec", new ProtocolCodecFilter(new ClientTextFactory()));
		getAcceptor().setHandler(new ClientHandler());
		//getAcceptor().setDefaultRemoteAddress(new InetSocketAddress("192.168.0.100",8888));// 设置默认访问地址  
		getAcceptor().setDefaultRemoteAddress(new InetSocketAddress(address,global.getConnectPort()));// 设置默认访问地址  
		getAcceptor().getSessionConfig().setIdleTime(IdleStatus.BOTH_IDLE, 150);

		KeepAliveMessageFactory heartBeatFactory = new KeepAliveMessageFactoryImpl();
		KeepAliveRequestTimeoutHandler heartBeatHandler = new KeepAliveRequestTimeoutHandlerImpl();
		KeepAliveFilter heartBeatFilter = new KeepAliveFilter(heartBeatFactory,IdleStatus.BOTH_IDLE, heartBeatHandler.CLOSE);
		//heartBeatFilter.setForwardEvent(true); //说明：继续调用 IoHandlerAdapter 中的 sessionIdle时间 
		heartBeatFilter.setRequestInterval(60); //说明：设置当连接的读取通道空闲的时候，心跳包请求时间间隔 
		heartBeatFilter.setRequestTimeout(20); //说明：设置心跳包请求后 等待反馈超时时间。 超过该时间后则调用KeepAliveRequestTimeoutHandler.CLOSE 
		getAcceptor().getFilterChain().addLast("heart", heartBeatFilter);

	}
	public void startClient() throws InterruptedException{
		for(;;){  
			try
			{
				Global global = Global.getInstance();
				try {

					address=java.net.InetAddress.getByName(global.getConnectAddr());
				} catch (UnknownHostException e) {
					// TODO Auto-generated catch block
					try {
						address = InetAddress.getLocalHost();
					} catch (UnknownHostException e1) {
						// TODO Auto-generated catch block
						e1.printStackTrace();
					}
					e.printStackTrace();

				}
				InetSocketAddress addr = new InetSocketAddress(address, 8888);
				future = getAcceptor().connect(addr);
				future.awaitUninterruptibly();
				session = future.getSession();


				ServerLogger.INFO("连接上位机成功");
				ServerMainFrame.getInstance().updataPcNetState(true);
				break;
			}catch(Exception e)
			{
				ServerMainFrame.getInstance().updataPcNetState(false);
				Thread.sleep(5000);
				ServerLogger.INFO("上位机未启动,重连中。。。");
				//getAcceptor().dispose();
			}
		}
	}
	
}
